
var viewer;
$(document).ready(async function () {

  const token = await getToken();
  if (token == null) return;
  const urn = await getUrnByBucketKey('smaple-001', token.access_token);
  if (urn == null) return;
  getObjectInfoByUrn(urn, token.access_token);

});

//获取token
async function getToken() {
  var data = await jQuery.post({
    url: 'https://developer.api.autodesk.com/authentication/v1/authenticate',
    headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
    data: {
      'client_id': 'xNMeq5TrwHJkGZQXAMXWGmE4KlwSRwYm',
      'client_secret': '4Eqfj5rqec7wEPAt',
      'grant_type': 'client_credentials',
      'scope': 'user-profile:read user:read user:write viewables:read data:read data:write data:create data:search bucket:create bucket:read bucket:update bucket:delete code:all account:read account:write',
    },
    success: function (res) {
      return res;
    },
    error: function (err) { //提示转换文件
      return null;
    }
  });
  return data == null ? null : data;
}

//根据bucketKey获取object urn
async function getUrnByBucketKey(bucketKey, token) {
  var data = await jQuery.get({
    url: 'https://developer.api.autodesk.com/oss/v2/buckets/' + bucketKey + '/objects',
    headers: { 'Authorization': 'Bearer ' + token },
    success: function (res) {
      console.log('getUrn', res);
      return res;
    },
    error: function (err) {
      console.error('getUrnError', err);
      return null;
    }
  });
  return data == null ? null : data.items[0].objectId;
}

//urnBase64获取object的清单
function getObjectInfoByUrn(urn, token) {
  var urnBase64 = btoa(encodeURI(urn));
  jQuery.ajax({
    url: 'https://developer.api.autodesk.com/modelderivative/v2/designdata/' + urnBase64 + '/manifest',
    headers: { 'Authorization': 'Bearer ' + token },
    success: function (res) {
      console.log('getObjectInfo', res);
      //完成了直接启动viewer
      if (res.status === 'success') launchViewer(urnBase64, token);
      else $("#forgeViewer").html('The translation job still running: ' + res.progress + '. Please try again in a moment.');
    },
    error: function (err) { //提示转换文件
      var msgButton = 'This file is not translated yet! ' +
        '<button class="btn btn-xs btn-info" onclick="translateObject()"><span class="glyphicon glyphicon-eye-open"></span> ' +
        'Start translation</button>'
      $("#forgeViewer").html(msgButton);
    }
  });
}



// 启动viewer
function launchViewer(urn, token) {
  var options = {
    /** env
     * AutodeskProduction,（default） 生产环境
     * AutodeskStaging,    阶段，缓存？
     * AutodeskDevelopment  开发环境
     */
    /** getAccessToken
     *  异步获取token的方法
     */
    env: 'AutodeskProduction',//*意思
    // getAccessToken: getForgeToken // 传了一个token和一个过期时间（单位为s）  
    accessToken: token
  };

  // viewer运行环境初始化
  Autodesk.Viewing.Initializer(options, () => {

    var config = {
      //Autodesk.DocumentBrowser:工具栏按钮添加一个文件夹，打开显示所有模型和图纸
      //Autodesk.CrossFadeEffects:颜色主题化、隐藏对象等之间的交叉淡入淡出
      //Autodesk.Edit2D:提供了实现2D矢量编辑的API。加载扩展不会添加UI或更改查看器。目的只是为其他扩展和客户端应用提供基础
      //Autodesk.Explode:使用其activate方法启用explode UI
      //Autodesk.Viewing.FusionOrbit:提供对动态观察工具的自定义。
      //Autodesk.Geolocation:提供将84坐标转换为查看器场景坐标的函数，然后再转换回来。支持加载到场景中的单个模型
      //Autodesk.BIM360.GestureDocumentNavigation:提供使用手势切换工作表和文档的选项
      /** Autodesk.glTF :view glTF 2.0 models in the Viewer.
         var options = {
         env: 'AutodeskProduction',
         api: 'derivativeV2',
         documentId: 'tests/unittest/models/gltf/duck.gltf'
         }
      */
      //Autodesk.Viewing.Popout：将查看器弹出到子窗口
      //Autodesk.BimWalk: 第一人称导航工具。-------默认
      //Autodesk.FullScreen: 全屏模式。------默认
      //Autodesk.Measure: 测量工具----默认
      //Autodesk.ModelStructure：模型浏览器按钮----默认
      //Autodesk.DefaultTools.NavTools: 平移----默认
      //Autodesk.PropertiesManager: 特性------默认
      //Autodesk.BIM360.RollCamera：相机-----默认
      //Autodesk.GoHome:使用其activate方法将相机设置为动画，使其恢复到原来的状态-----默认
      //Autodesk.Section：截面分析？----默认
      //Autodesk.ViewerSettings：设置-----默认
      //Autodesk.Viewing.ZoomWindow：缩放----默认
      //Autodesk.Hyperlink:通过添加画布工具提示来增强二维模型，单击该提示可导航
      //Autodesk.LayerManager:使用其activate方法打开LayerPanel UI。
      //Autodesk.PDF：注册文件加载器，使viewer.loadModel()能够加载pdf文件，查看器将一次呈现一个页面
      //ModelBuilder 动态模型构造器Autodesk.Viewing.Extensions.SceneBuilder#addNewModel
      //Autodesk.Viewing.SceneBuilder： 场景构建器无需从URL加载场景
      //Autodesk.Snapping：提供对Autodesk应用程序的访问的实用程序扩展
      //Autodesk.SplitScreen：将LMV画布细分为2到4个（含）独立的子画布
      //Autodesk.ViewCubeUi：创建ViewCube的UI
      //Autodesk.Viewing.Wireframes：提供以线框模式渲染模型的功能。实现的方法性能不是很好，因此最好避免在大型模型中使用它。
      //Autodesk.BIM360.Minimap：

      extensions: [
        // "Autodesk.AEC.Minimap3DExtension"
      ]
    }

    //GuiViwer3D  create a viewer object with UI elements, including a toolbar.
    var domContainer = document.getElementById('forgeViewer');
    viewer = new Autodesk.Viewing.GuiViewer3D(domContainer, config);

    //注册外部扩展   引入外部扩展的意义是什么？
    // Autodesk.Viewing.theExtensionManager.registerExternalExtension(
    //   'MyExternal.Extension.Id',
    //   'http://localhost:3000/extensions/external.js');


    // @1 在加载几何图形完成时卸载默认扩展模块
    viewer.addEventListener(Autodesk.Viewing.GEOMETRY_LOADED_EVENT, (x) => {
      //卸载naviTool扩展
      // let navExtension = viewer.getExtension('Autodesk.DefaultTools.NavTools');
      // navExtension.unload();
      //加载外部扩展
      // viewer.loadExtension('MyExternal.Extension.Id').then(
      //   function (externalExtension) {
      //     externalExtension.sayHello('Bob')
      //   })

      // viewer.loadExtension('Autodesk.BIM360.Minimap');

    });

    // viewer.addEventListener(Autodesk.Viewing.TEXTURES_LOADED_EVENT, () => {
    //   viewer.getExtension('Autodesk.BimWalk').activate();
    // });

    // @2 取消注册阻止加载（报错：Has it been registered？因为查看器仍在尝试加载扩展。但查看器仍将按预期取消注册）
    //theExtensionManager单例用来注册内外部extension 获取extension实例以及判断extension是否有效
    // Autodesk.Viewing.theExtensionManager.unregisterExtension('Autodesk.PropertiesManager');
    // Autodesk.Viewing.theExtensionManager.unregisterExtension('Autodesk.ViewerSettings');


    viewer.start();
    var documentId = 'urn:' + urn;
    //加载清单数据load(文件urn, 成功回调, 失败回调, 配置)
    Autodesk.Viewing.Document.load(documentId, onSuccess, onFailure);
  });
}

function onSuccess(doc) {
  // doc  允许客户端从云中加载模型数据，它允许访问根目录，并提供一种按id查找元素的方法。
  //doc.getRoot 返回一个BubbleNode实例，封装当前文档清单JSON。
  var viewables = doc.getRoot().getDefaultGeometry();
  viewer.loadDocumentNode(doc, viewables).then(i => {
    //loadFinish
    doc.downloadAecModelData();
    viewer.loadExtension('Autodesk.AEC.Minimap3DExtension');
  });
}

function onFailure(viewerErrorCode, viewerErrorMsg) {
  console.error('onDocumentLoadFailure() - errorCode:' + viewerErrorCode + '\n- errorMessage:' + viewerErrorMsg);
}

async function getForgeToken(callback) {
  const token = await getToken();
  callback(token.access_token, token.expires_in)
}
